import os
import hashlib
import markdown
import datetime
from urllib.parse import urlparse
from django import template
from django.template.defaultfilters import stringfilter
from django.utils.safestring import mark_safe
from ..IpInfo import ip_protect as protect

register = template.Library()  # 自定义filter时必须加上


@register.filter(is_safe=True)  # 注册template filter
@stringfilter  # 希望字符串作为参数
def custom_markdown(value):
    return mark_safe(markdown.markdown(value,
                                       extensions=['markdown.extensions.fenced_code', 'markdown.extensions.codehilite',
                                                   'markdown.extensions.footnotes', 'markdown.extensions.toc',
                                                   'pymdownx.githubemoji', 'markdown.extensions.tables',
                                                   'pymdownx.tasklist', 'pymdownx.headeranchor',
                                                   'pymdownx.githubemoji'],
                                       safe_mode=False, enable_attributes=True))


@register.filter
def get_visitor_url(visitor):
    return urlparse(visitor.url, scheme='http').geturl() if visitor.url else 'javascript:void(0);'


@register.filter(is_safe=True)
def sub_content(content, length):
    content = content.replace('[TOC]\n', '')
    if len(content) <= length:
        show_content = content
    elif content[:length].count('```') % 2 == 1:
        start = content[:length].rindex('```') + 1
        try:
            end = content.index('```', start)
            if end - start > 200:
                if start < 100:
                    p = content.index('\n', length)
                    show_content = content[:p + 1] + '```\n\n...'
                else:
                    show_content = content[:start - 1] + '\n\n...'
            else:
                show_content = content[:end + 3] + '\n\n...'
        except ValueError:
            show_content = content[:length] + '\n\n...'
    else:
        show_content = content[:length] + '\n\n...'

    return show_content


@register.filter
def ip_protect(ip):
    return protect(ip)


@register.filter
def filter_row(count):
    return 'row1' if count % 2 == 1 else 'row2'


@register.filter(is_safe=True)
def escape_content(content):
    return content.replace('\r', '\\r').replace('\n', '\\n')


@register.filter
def tags_namelist(tags):
    return ' / '.join([tag.tag_name for tag in tags])


@register.filter
def mod(value1, value2):
    if int(value2) == 0:
        return 0
    return int(value1) % int(value2)


@register.filter
def visitor_nickname(visitor):
    return visitor.nickname + ip_protect(visitor.ip_address) + '[' + visitor.city + ']'


@register.filter
def percentage(value, total):
    if total == 0:
        return '0.0%'
    return str(round(value * 100 / total, 1)) + '%'


@register.filter
def length_percentage(list1, list2):
    return percentage(len(list1), len(list2))


@register.filter
def table_class(counter):
    class_map = {1: 'active', 3: 'success', 5: 'info', 7: 'warning', 9: 'danger'}
    return class_map[counter] if counter in class_map else ''


@register.filter
def doughnut_color(counter):
    color_map = {1: '#f5f5f5', 3: '#dff0d8', 5: '#d9edf7', 7: '#fcf8e3', 9: '#f2dede'}
    return color_map[counter] if counter in color_map else '#ffffff'


@register.filter
def get_day_delta(dates, key):
    try:
        to_date = datetime.datetime.strptime(dates[key], '%Y-%m-%d')
    except KeyError:
        return 8888
    else:
        return abs((datetime.datetime.now() - to_date).days)


@register.filter
def gravatar(email):
    code = email or os.urandom(32).decode('latin1')
    return "https://cdn.v2ex.com/gravatar/" + hashlib.md5(code.encode().lower()).hexdigest() + "?d=retro"


@register.filter
def iter_pages(page):
    if page.paginator.num_pages <= 10:
        return list(range(1, page.paginator.num_pages + 1))
    else:
        return list(range(1, 6)) + [None] + list(range(page.paginator.num_pages - 1, page.paginator.num_pages + 1))
